package jp.seraph.same.view;

import java.awt.Dimension;
import java.awt.event.ComponentEvent;
import java.awt.event.ComponentListener;

import javax.swing.DefaultListModel;
import javax.swing.JList;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.ListSelectionModel;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;

import jp.seraph.same.controller.PoseController;
import jp.seraph.same.model.PoseCollectionModel;
import jp.seraph.same.model.PoseCollectionModelListener;

/**
 * ポーズのリスト表示・選択を管理するパネル
 * 
 */
public class PoseListPanel extends JPanel implements PoseCollectionModelListener {
    public PoseListPanel(PoseCollectionModel aModel, PoseController aController) {
        mModel = aModel;
        mListModel = new DefaultListModel();
        mPoseList = new JList(mListModel);
        mPoseList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
        // mPoseList.setPreferredSize(null);
        mScrollPane = new JScrollPane();
        mScrollPane.setViewportView(mPoseList);

        mController = aController;

        // Viewからの変更通知
        mPoseList.addListSelectionListener(new ListSelectionListener() {
            public void valueChanged(ListSelectionEvent e) {
                Object tSelectedValue = mPoseList.getSelectedValue();
                if (tSelectedValue == null || mModel.getSelectedPoseName().equals(tSelectedValue))
                    return; // 現在のModel側の選択状況と変わってなければ何もしない

                mController.selectPose((String) tSelectedValue);
            }
        });

        mModel.addListener(this);

        this.add(mScrollPane);
        this.addComponentListener(new ComponentListener() {

            /**
             * 
             * @see java.awt.event.ComponentListener#componentHidden(java.awt.event.ComponentEvent)
             */

            public void componentHidden(ComponentEvent e) {
            }

            /**
             * 
             * @see java.awt.event.ComponentListener#componentMoved(java.awt.event.ComponentEvent)
             */

            public void componentMoved(ComponentEvent e) {
            }

            /**
             * 
             * @see java.awt.event.ComponentListener#componentResized(java.awt.event.ComponentEvent)
             */

            public void componentResized(ComponentEvent e) {
                PoseListPanel.this.refresh();
            }

            /**
             * 
             * @see java.awt.event.ComponentListener#componentShown(java.awt.event.ComponentEvent)
             */

            public void componentShown(ComponentEvent e) {
                PoseListPanel.this.refresh();
            }

        });
    }

    /**
     * モデルからの変更通知
     * 
     * @see jp.seraph.same.model.PoseCollectionModelListener#PoseCountChanged(jp.seraph.same.model.PoseModel)
     */

    public void PoseCountChanged(PoseCollectionModel sender) {
        this.refresh();
    }

    /**
     * モデルからの変更通知 モデルでの選択状況が変更されたら、Viewもそのように変更してやる。
     * 
     * @see jp.seraph.same.model.PoseCollectionModelListener#SelectedPoseChanged(jp.seraph.same.model.PoseModel,
     *      int, java.lang.String)
     */

    public void SelectedPoseChanged(PoseCollectionModel sender, int index, String poseName) {
        Object tSelectedValue = mPoseList.getSelectedValue();
        if (poseName == null || poseName.equals(tSelectedValue))
            return;

        mPoseList.setSelectedIndex(index);
    }

    private PoseCollectionModel mModel;
    private PoseController mController;
    private JScrollPane mScrollPane;
    private JList mPoseList;
    private DefaultListModel mListModel;
    private static final long serialVersionUID = 10L;

    private void refresh() {
        mListModel.clear();

        int tCount = mModel.getPoseCount();
        for (int i = 0; i < tCount; i++) {
            String tName = mModel.getPoseName(i);
            mListModel.addElement(tName);
        }

        mScrollPane.setViewportView(mPoseList);
        // this.doLayout();
        mScrollPane.setSize(new Dimension(this.getWidth() - 5, this.getHeight() - 5));
        mScrollPane.setPreferredSize(new Dimension(this.getWidth() - 5, this.getHeight() - 5));
    }
}
